﻿using Inovout.Cloud.Data.Blob.Models;
using Inovout.Cloud.Data.Blob.Service;
using Inovout.Cloud.Models;
using Inovout.Cloud.Storage.Models;
using Inovout.Services;
using NHibernate.Criterion;
using System.Collections.Generic;
using System.Threading;
using Inovout.Security;
using Inovout.Cloud.Namespace.Services;
using Inovout.Cloud.Namespace.Models;
using Inovout.Runtime;

namespace Inovout.Cloud.Storage.Services
{
    public class BucketService : RepositoryService<Bucket>, IBucketService
    {
        IDirectoryService directoryService;
        IApplication application;
        public BucketService(IDirectoryService directoryService)
        {
            this.directoryService = directoryService;
            application = ComponentRegistry.Resolve<IApplication>();
        }
        private Directory GetBucketFolder(Project project, Bucket bucket)
        {
            string bucketFolderPath = string.Format("/user/{0}/projects/{1}/{2}",
                Thread.CurrentPrincipal.Identity.Name.ToString().ToLower(),
                project.Name, bucket.Name);
            Directory bucketFolder = directoryService.FindByPath(bucketFolderPath);
            if (bucketFolder == null)
            {
                bucketFolder = directoryService.Create(bucketFolderPath);
            }
            return bucketFolder;
        }

        private Directory GetBucketLocalFolder(Project project, Bucket bucket)
        {  
            string bucketFolderPath = string.Format(application.Settings["LocalRootPath"].ToString(),
                Thread.CurrentPrincipal.Identity.Name.ToString().ToLower(),
                project.Name, bucket.Name);
            Directory bucketFolder = directoryService.FindByPath(bucketFolderPath);
            if (bucketFolder == null)
            {
                bucketFolder = directoryService.Create(bucketFolderPath);
            }
            return bucketFolder;
        }

        public override void Save(Bucket entity)
        {
           // entity.Folder = GetBucketFolder(entity.Project, entity);
            entity.Folder = GetBucketLocalFolder(entity.Project, entity);
            //在namespaceDatabase不存在，必须在namespace 中创建  
            if (this.Exists(entity.Name))
            {
                Node node = new Node() { Category = NodeCategories.DataSource, Path = entity.Name };
                NodeService nodeService = (NodeService)ComponentRegistry.Resolve<INodeService>();
                nodeService.Save(node);
            }
            base.Save(entity);
        }

        public Bucket FindByName(string bucketName)
        {
            return base.Repository.Find(Restrictions.Eq("Name", bucketName).IgnoreCase());
        }
        public IEnumerable<Bucket> FindAllByProject(Project project)
        {
            return base.Repository.FindAll(Restrictions.Eq("Project.Id", project.Id));
        }

        public void Delete(string bucketName)
        {
            Bucket bucket = FindByName(bucketName);
            if (bucket.Folder.Children.Count > 0)
            {
                throw new System.ArgumentException("Permanently deletes an empty bucket.");
            }
            Repository.Delete((object)bucket.Id);
            directoryService.Delete(bucket.Folder);
        }

        /// <summary>
        /// 判断数据库是否存在
        /// </summary>
        /// <param name="category">namespace</param>
        /// <param name="path">数据库地址</param>
        public bool Exists(string path)
        {
            //namespace中是否已存在
            NodeService nodeService = (NodeService)ComponentRegistry.Resolve<INodeService>();
            if (nodeService.Exists(NodeCategories.DataSource, path))
            {
                //不存在
                return true;
            }
            else
            {
                return false;
            }

        }
    }
}
